/*
 * Copyright (c) 2022 Huawei Device Co., Ltd.
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

#ifndef OHOS_AVSESSION_H
#define OHOS_AVSESSION_H

/**
 * @addtogroup avsession
 * @{
 *
 * @brief Provides APIs for audio and video (AV) media control.
 *
 * The APIs can be used to create, manage, and control media sessions.
 *
 * @syscap SystemCapability.Multimedia.AVSession.Core
 * @since 9
 * @version 1.0
 */

/**
 * @file av_session.h
 *
 * @brief Declares APIs for setting and obtaining sessions.
 *
 * @since 9
 * @version 1.0
 */

#include <string>
#include <memory>

#include "avsession_info.h"
#include "want_agent.h"
#include "avsession_controller.h"

namespace OHOS::AVSession {
/**
 * @brief Represents a session object that provides APIs for configuring session attributes
 * and proactively updating the playback state and session metadata.
 */
class AVSession {
public:

    /**
     * @brief Enumerates the session types.
     *
     * @since 9
     * @version 1.0
     */
    enum {
        /** Invalid session. */
        SESSION_TYPE_INVALID = -1,
        /** Audio session. */
        SESSION_TYPE_AUDIO = 0,
        /** Video session. */
        SESSION_TYPE_VIDEO = 1
    };

    /**
     * @brief Obtains the session ID.
     *
     * @return Returns the session ID.
     * @since 9
     * @version 1.0
     */
    virtual std::string GetSessionId() = 0;

    /**
     * @brief Obtains the session metadata.
     *
     * @param meta Indicates the pointer to the metadata, which is an {@link AVMetaData} object.
     * @return Returns {@link #AVSESSION_SUCCESS} if the operation is successful; returns an error code otherwise.
     * @see SetAVMetaData
     * @since 9
     * @version 1.0
     */
    virtual int32_t GetAVMetaData(AVMetaData& meta) = 0;

    /**
     * @brief Sets session metadata.
     *
     * @param meta Indicates the pointer to the new metadata, which is an {@link AVMetaData} object.
     * @return Returns {@link #AVSESSION_SUCCESS} if the operation is successful; returns an error code otherwise.
     * @see GetAVMetaData
     * @since 9
     * @version 1.0
     */
    virtual int32_t SetAVMetaData(const AVMetaData& meta) = 0;

    /**
     * @brief Obtains the playback state.
     *
     * @param state Indicates the pointer to the playback state, which is an {@link AVPlaybackState} object.
     * @return Returns {@link #AVSESSION_SUCCESS} if the operation is successful; returns an error code otherwise.
     * @see SetAVPlaybackState
     * @since 9
     * @version 1.0
     */
    virtual int32_t GetAVPlaybackState(AVPlaybackState& state) = 0;

    /**
     * @brief Sets a playback state.
     *
     * @param state Indicates the pointer to the new playback state, which is an {@link AVPlaybackState} object.
     * @return Returns {@link #AVSESSION_SUCCESS} if the operation is successful; returns an error code otherwise.
     * @see GetAVPlaybackState
     * @since 9
     * @version 1.0
     */
    virtual int32_t SetAVPlaybackState(const AVPlaybackState& state) = 0;

    /**
     * @brief Sets a {@code WantAgent} object to start the ability of this session.
     *
     * @param ability Indicates the pointer to the ability, which is an {@link AbilityRuntime::WantAgent::WantAgent} object.
     * @return Returns {@link #AVSESSION_SUCCESS} if the operation is successful; returns an error code otherwise.
     * @see AVSessionController#GetLaunchAbility
     * @since 9
     * @version 1.0
     */
    virtual int32_t SetLaunchAbility(const AbilityRuntime::WantAgent::WantAgent& ability) = 0;

    /**
     * @brief Obtains the session controller.
     *
     * @return Returns the pointer to the session controller, which is an {@link AVSessionController} object.
     * @since 9
     * @version 1.0
     */
    virtual std::shared_ptr<AVSessionController> GetController() = 0;

    /**
     * @brief Registers a callback for this session.
     *
     * @param callback Indicates the pointer to the callback, which is an {@link AVSessionCallback} object.
     * @return Returns {@link #AVSESSION_SUCCESS} if the operation is successful; returns an error code otherwise.
     * @since 9
     * @version 1.0
     */
    virtual int32_t RegisterCallback(const std::shared_ptr<AVSessionCallback>& callback) = 0;

    /**
     * @brief Activates this session.
     *
     * A session can receive control commands only after it is activated.
     *
     * @return Returns {@link #AVSESSION_SUCCESS} if the operation is successful; returns an error code otherwise.
     * @see Deactivate
     * @see IsActive
     * @since 9
     * @version 1.0
     */
    virtual int32_t Activate() = 0;

    /**
     * @brief Deactivates this session.
     *
     * A session cannot receive control commands after it is deactivated.
     *
     * @return Returns {@link #AVSESSION_SUCCESS} if the operation is successful; returns an error code otherwise.
     * @see Activate
     * @see IsActive
     * @since 9
     * @version 1.0
     */
    virtual int32_t Deactivate() = 0;

    /**
     * @brief Checks whether this session is activated.
     *
     * @return Returns <b>true> if the session is activated; returns <b>false</b> otherwise.
     * @see Activate
     * @see Deactivate
     * @since 9
     * @version 1.0
     */
    virtual bool IsActive() = 0;

    /**
     * @brief Destroys this session.
     *
     * Before creating a session, you must destroy the existing session.
     *
     * @return Returns {@link #AVSESSION_SUCCESS} if the operation is successful; returns an error code otherwise.
     * @since 9
     * @version 1.0
     */
    virtual int32_t Destroy() = 0;

    /**
     * @brief Adds a supported control command.
     *
     * @param cmd Indicates the control command to add.
     * The value must be within the range from {@link #SESSION_CMD_INVALID} to {@link #SESSION_CMD_MAX}.
     * @return Returns {@link #AVSESSION_SUCCESS} if the operation is successful; returns an error code otherwise.
     * @since 9
     * @version 1.0
     */
    virtual int32_t AddSupportCommand(const int32_t cmd) = 0;

    /**
     * @brief Deletes a supported control command.
     *
     * @param cmd Indicates the control command to delete. 
     * The value must be within the range from {@link #SESSION_CMD_INVALID} to {@link #SESSION_CMD_MAX}.
     * @return Returns {@link #AVSESSION_SUCCESS} if the operation is successful; returns an error code otherwise.
     * @since 9
     * @version 1.0
     */
    virtual int32_t DeleteSupportCommand(const int32_t cmd) = 0;

    virtual ~AVSession() = default;
};
} // namespace OHOS::AVSession
/** @} */
#endif // OHOS_AVSESSION_H
